package com.seguriapp.gwt.server;

import static com.google.common.collect.Lists.newArrayList;

import java.util.List;

import net.customware.gwt.dispatch.server.ExecutionContext;
import net.customware.gwt.dispatch.shared.DispatchException;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;

import org.apache.log4j.Logger;
import org.restlet.data.MediaType;
import org.restlet.resource.ClientResource;

import com.seguriapp.common.config.GlobalConfigLoader;
import com.seguriapp.common.gwt.server.AbstractSeguriAppHandler;
import com.seguriapp.common.security.SeguriAppUser;
import com.seguriapp.entities.MenuLink;
import com.seguriapp.entities.User;
import com.seguriapp.gwt.shared.GetInitialDataAction;
import com.seguriapp.gwt.shared.GetInitialDataResult;

public class GetInitialDataHandler extends AbstractSeguriAppHandler<GetInitialDataAction, GetInitialDataResult> {

  private static final Logger LOGGER = Logger.getLogger(GetInitialDataHandler.class);

  public Class<GetInitialDataAction> getActionType() {
    return GetInitialDataAction.class;
  }

  public GetInitialDataResult execute(GetInitialDataAction action, ExecutionContext context) throws DispatchException {

    final GetInitialDataResult result = new GetInitialDataResult();
    try {
      final User user = SeguriAppUser.getSeguriAppSecureUser() != null ? SeguriAppUser.getSeguriAppSecureUser().getSeguriAppUser() : null;
      if (user == null) {
        final String serverUrl = GlobalConfigLoader.getInstance().getGlobalConfig().getBackEndUrl();
        final String url = serverUrl.concat(GlobalConfigLoader.getInstance().getGlobalConfig().getGetMenuLinks());
        final ClientResource resource = new ClientResource(String.format(url, action.getRole()));
        final String menuLinksListJs = resource.get(MediaType.TEXT_PLAIN).getText();
        LOGGER.info("Data received : \n" + menuLinksListJs);
        result.setMenuLinks(getJsonDataFromString(menuLinksListJs));
      } else {
        result.setMenuLinks(SeguriAppUser.getSeguriAppSecureUser().getMenuLinks());
        result.setUser(user);
      }
    } catch (Exception e) {
      LOGGER.error("Error obtaining the initial data \n", e);
    }
    return result;
  }

  private List<MenuLink> getJsonDataFromString(final String menuLinksListJs) {
    final List<MenuLink> menuLinksList = newArrayList();
    final JSONObject root = JSONObject.fromObject(menuLinksListJs);
    JSONArray dataArray = null;
    JSONObject jo = null;
    if (root.has("menuLinks")) {
      dataArray = root.getJSONArray("menuLinks");
      if (dataArray != null) {
        for (int i = 0; i < dataArray.size(); i++) {
          jo = dataArray.getJSONObject(i);
          final MenuLink menuLink = processjSONObject(jo);
          if (menuLink != null){
            menuLinksList.add(menuLink);
          }
        }
      }
    }
    return menuLinksList;
  }

  private MenuLink processjSONObject(final JSONObject jo) {
    if (jo.has("id") && jo.has("name") && jo.has("path")) {
      final MenuLink menuLink = new MenuLink();
      menuLink.setId(jo.getLong("id"));
      menuLink.setName(jo.getString("name"));
      menuLink.setPath(jo.getString("path"));
      return menuLink;
    }
    return null;
  }

}
